﻿

using System;
using System.Collections;
using System.Collections.Generic;

namespace Test30.Engine
{
    public class Inventory : ICollection<Item>, IItemCollection
    {
        public readonly GameEvent<Item, EventArgs> ItemAdded = new GameEvent<Item, EventArgs>();
        public readonly GameEvent<Item, EventArgs> ItemRemoved = new GameEvent<Item, EventArgs>();
        public readonly GameEvent<Item, EventArgs> ItemChanged = new GameEvent<Item, EventArgs>();
        public int Count => _items.Count;
        public int Max => 20;
        public bool IsReadOnly => false;
        public Item this[int index]
        {
            get
            {
                // allow out of bounds checks
                if (index >= Count) return null;

                return _items[index];
            }
        }
        public Inventory()
        {
            _items = new List<Item>();
        }
        public IEnumerator<Item> GetEnumerator()
        {
            return _items.GetEnumerator();
        }

        IEnumerator IEnumerable.GetEnumerator()
        {
            return GetEnumerator();
        }

        public void Add(Item item)
        {
            if (Count >= Max) throw new InvalidOperationException("Cannot add any more items to the inventory.");

            _items.Add(item);
            _items.Sort();

            if (item != null)
            {
                item.Changed += Item_Changed;

                ItemAdded.Raise(item, EventArgs.Empty);
            }
        }

        public void Clear()
        {
            while (_items.Count > 0)
            {
                RemoveAt(_items.Count - 1);
            }
        }
        public void RemoveAt(int index)
        {
            Item item = _items[index];

            item.Changed -= Item_Changed;

            _items.RemoveAt(index);

            ItemRemoved.Raise(item, EventArgs.Empty);
        }

        public bool Contains(Item item)
        {
            return _items.Contains(item);
        }

        public void CopyTo(Item[] array, int arrayIndex)
        {
            throw new NotImplementedException();
        }

        public bool Remove(Item item)
        {
            if (item != null)
            {
                item.Changed -= Item_Changed;

                bool result = _items.Remove(item);

                ItemRemoved.Raise(item, EventArgs.Empty);

                return result;
            }
            return false;
        }


        public string GetCategory(int index)
        {
            return String.Empty;
        }

        private void Item_Changed(object sender, EventArgs e)
        {
            ItemChanged.Raise((Item)sender, EventArgs.Empty);
        }

        int IItemCollection.Count => Count;
        int ICollection<Item>.Count => Count;


        private readonly List<Item> _items;  
    }
}
